package com.hnist.empdemo.service.Impl;

import com.hnist.empdemo.common.Config;
import com.hnist.empdemo.mapper.Impl.employMapperImpl;
import com.hnist.empdemo.pojo.Department;
import com.hnist.empdemo.pojo.Employee;
import com.hnist.empdemo.pojo.Position;
import org.apache.poi.ss.usermodel.Cell;
import org.apache.poi.ss.usermodel.Row;
import org.apache.poi.ss.usermodel.Sheet;
import org.apache.poi.ss.usermodel.Workbook;
import org.apache.poi.xssf.usermodel.XSSFWorkbook;
import org.apache.poi.ss.usermodel.CellType;


import java.io.FileOutputStream;
import java.io.IOException;
import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;

public class employServiceImpl {

    private static employServiceImpl employService = new employServiceImpl();

    private employServiceImpl() {
    }

    /**
     * 单例模式,提供唯一employService实例
     * @return
     */
    public static employServiceImpl getInstance() {
        return employService;
    }

    /**
     * 列表展示部门Or职位Or员工的所有信息，如果返回的列表为空，请提示数据不存在(Constant.DATA_NOT_FOUND_ERROR)
     *      调用示例：获取所有部门信息
     *     List<Department> departments = employServiceImpl.getInstance().listAllDeptOrPosOrEmpInfo(Department.class);
     *     条件查询部门信息
     *     List<Department> departments = employServiceImpl.getInstance().listAllDeptOrPosOrEmpInfo(Department.class, employee);
     *      调用示例：获取所有职位信息
     *     List<Position> positions = employServiceImpl.getInstance().listAllDeptOrPosOrEmpInfo(Position.class);
     *     条件查询职位信息
     *     List<Position> positions = employServiceImpl.getInstance().listAllDeptOrPosOrEmpInfo(Position.class, employee);
     *     调用示例：获取所有员工信息
     *     List<Employee> employees = employServiceImpl.getInstance().listAllDeptOrPosOrEmpInfo(Employee.class);
     *     条件查询员工信息
     *     List<Employee> employees = employServiceImpl.getInstance().listAllDeptOrPosOrEmpInfo(Employee.class, employee);
     * @param clazz
     * @param employees
     * @return
     * @param <T>
     */
    public <T> List<T> listAllDeptOrPosOrEmpInfo(Class<T> clazz, Employee... employees) {
        Employee employee = (employees.length > 0) ? employees[0] : new Employee();
        List<Employee> employeeList = employMapperImpl.getInstance().queryEmpInfo(employee);
        List<T> list = new ArrayList<>();
        if(clazz == null) {
            throw new NullPointerException("clazz cannot be null");
        }
        employeeList.forEach(emp -> {
            if(clazz == Department.class) {
                Department department = new Department();
                department.setName(emp.getDepartment());
                list.add((T) department);
            } else if(clazz == Position.class) {
                Position position = new Position();
                position.setName(emp.getPosition());
                list.add((T) position);
            } else {
                list.add((T) emp);
            }
        });
        return list;
    }

    public <T> List<String> listDistinctDeptOrPos(Class<T> clazz) {
        List<Employee> employeeList = listAllDeptOrPosOrEmpInfo(Employee.class);
        List<String> list = new ArrayList<>();
        if(clazz == Department.class) {
            list = employeeList.stream().map(Employee::getDepartment).distinct().collect(Collectors.toList());
        }
        if(clazz == Position.class) {
            list = employeeList.stream().map(Employee::getPosition).distinct().collect(Collectors.toList());
        }
        return list;
    }

    /**
     * 添加员工信息,如果返回true请提示数据添加成功(Constant.DATA_ADD_SUCCESS)，否则请提示数据已存在(Constant.DATA_DUPLICATE_ERROR)
     * @param employee
     * @return
     */
    public Boolean addEmployee(Employee employee) {
        return employMapperImpl.getInstance().addEmployee(employee);
    }

    /**
     * 删除员工信息,如果返回true请提示数据删除成功(Constant.DATA_DELETE_SUCCESS)，否则请提示数据不存在(Constant.DATA_NOT_FOUND_ERROR)
     * @param id
     * @return
     */
    public Boolean deleteEmployeeById(int id) {
        return employMapperImpl.getInstance().deleteEmployeeById(id);
    }

    /**
     * 修改员工信息,如果返回true请提示数据修改成功(Constant.DATA_UPDATE_SUCCESS)，否则请提示数据修改失败(Constant.DATA_UPDATE_ERROR)
     * @param employee
     * @return
     */
    public Boolean updateEmployee(Employee employee) {
        return employMapperImpl.getInstance().updateEmployee(employee);
    }

    public boolean isEmployeeIdExists(Integer id) {
        // 实现检查员工ID是否存在的逻辑
        // 这里假设你有一个获取所有员工的方法 listAllDeptOrPosOrEmpInfo(Employee.class)
        List<Employee> employees = listAllDeptOrPosOrEmpInfo(Employee.class);
        return employees.stream().anyMatch(emp -> emp.getId() == id);
    }

    /**
     * 统计功能：能根据多种参数进行人员的统计。例如，统计四类人员数量以及总数， 或者统计男、女员工的数量等信息。
     * @return Map对象，key为统计参数，value为统计结果
     */
    public Map<String, Integer> countEmployees() {
        List<Employee> employees = listAllDeptOrPosOrEmpInfo(Employee.class, new Employee());
        //统计四类人员各自数量
        Map<String, Integer> countMap = new HashMap<>();
        countMap.put("员工总数", employees.size());
        countMap.put("男", employees.stream().filter(employee -> "男".equals(employee.getGender())).collect(Collectors.toList()).size());
        countMap.put("女", employees.stream().filter(employee -> "女".equals(employee.getGender())).collect(Collectors.toList()).size());
        countMap.put("经理", employees.stream().filter(employee -> "经理".equals(employee.getPosition())).collect(Collectors.toList()).size());
        countMap.put("技术人员", employees.stream().filter(employee -> "技术人员".equals(employee.getPosition())).collect(Collectors.toList()).size());
        countMap.put("销售", employees.stream().filter(employee -> "销售".equals(employee.getPosition())).collect(Collectors.toList()).size());
        countMap.put("销售经理", employees.stream().filter(employee -> "销售经理".equals(employee.getPosition())).collect(Collectors.toList()).size());
        return countMap;
    }

    /**
     * 保存功能：可将当前系统中各类人员记录存入excel文件中，存入方式任意。
     * 使用Apache POI库将员工信息导出到Excel文件
     * @throws IOException 文件操作异常
     */
    public void saveInfoToFile() {
        // 获取所有员工信息
        List<Employee> employees = listAllDeptOrPosOrEmpInfo(Employee.class);

        if (employees.isEmpty()) {
            System.out.println("没有员工数据可保存！");
            return;
        }

        // 创建工作簿
        try (Workbook workbook = new XSSFWorkbook()) {
            // 创建工作表
            Sheet sheet = workbook.createSheet("员工信息");

            // 创建表头
            Row headerRow = sheet.createRow(0);
            String[] headers = {"ID", "姓名", "性别", "部门", "职位", "薪资", "奖金"};

            for (int i = 0; i < headers.length; i++) {
                Cell cell = headerRow.createCell(i);
                cell.setCellValue(headers[i]);
            }

            // 写入员工数据
            for (int i = 0; i < employees.size(); i++) {
                Employee employee = employees.get(i);
                Row row = sheet.createRow(i + 1);

                row.createCell(0).setCellValue(employee.getId());
                row.createCell(1).setCellValue(employee.getName());
                row.createCell(2).setCellValue(employee.getGender());
                row.createCell(3).setCellValue(employee.getDepartment());
                row.createCell(4).setCellValue(employee.getPosition());
                row.createCell(5).setCellValue(employee.getSalary());
                row.createCell(6).setCellValue(employee.getBonus());
            }
            int cnt = 0;
            while(true) {
                Path path = Paths.get(Config.File_SAVE_PATH + "员工信息表" + "{" + cnt + "}" + ".xlsx");
                if(Files.exists(path)) {
                    cnt++;
                }else{
                    break;
                }
            }
            // 写入文件
            try (FileOutputStream fileOut = new FileOutputStream(Config.File_SAVE_PATH + "员工信息表" + "{" + cnt + "}" + ".xlsx")) {
                workbook.write(fileOut);
                System.out.println("员工信息已成功保存到文件：" + Config.File_SAVE_PATH + "员工信息表" + "{" + cnt + "}" + ".xlsx");
            }
        } catch (IOException e) {
            System.err.println("保存员工信息失败：" + e.getMessage());
        }
    }

    /**
     * 读取功能：可将保存在excel文件中的人员信息读入到当前系统中，供用户进行使用。
     */
    public void readInfoFromFile(String filePath) {
        // 基本验证
        if (filePath == null || filePath.isEmpty()) {
            System.out.println("文件路径不能为空！");
            return;
        }

        Path path = Paths.get(filePath);
        if (!Files.exists(path)) {
            System.out.println("指定的文件不存在：" + filePath);
            return;
        }

        // 文件扩展名验证
        String fileName = filePath.toLowerCase();
        if (!fileName.endsWith(".xlsx") && !fileName.endsWith(".xls")) {
            throw new IllegalArgumentException("文件格式不正确，请选择Excel文件(.xlsx或.xls)");
        }

        try (Workbook workbook = new XSSFWorkbook(Files.newInputStream(path))) {
            Sheet sheet = workbook.getSheetAt(0);

            // 检查表头
            if (sheet.getLastRowNum() < 1) {
                throw new IllegalArgumentException("文件格式不正确：缺少表头或数据行");
            }

            Row headerRow = sheet.getRow(0);
            if (headerRow == null) {
                throw new IllegalArgumentException("文件格式不正确：缺少表头");
            }

            // 验证表头内容
            String[] expectedHeaders = {"ID", "姓名", "性别", "部门", "职位", "薪资", "奖金"};
            if (headerRow.getLastCellNum() < expectedHeaders.length) {
                throw new IllegalArgumentException("文件格式不正确：表头列数不足");
            }

            // 检查表头是否匹配
            for (int i = 0; i < expectedHeaders.length; i++) {
                Cell cell = headerRow.getCell(i);
                if (cell == null || !expectedHeaders[i].equals(cell.getStringCellValue())) {
                    throw new IllegalArgumentException("文件格式不正确：表头第" + (i+1) + "列应为'" + expectedHeaders[i] + "'");
                }
            }

            // 跳过表头行，从第二行开始读取数据
            for (int i = 1; i <= sheet.getLastRowNum(); i++) {
                Row row = sheet.getRow(i);
                if (row == null) continue;

                // 读取每行的单元格数据
                Cell idCell = row.getCell(0);
                Cell nameCell = row.getCell(1);
                Cell genderCell = row.getCell(2);
                Cell departmentCell = row.getCell(3);
                Cell positionCell = row.getCell(4);
                Cell salaryCell = row.getCell(5);
                Cell bonusCell = row.getCell(6);

                // 创建员工对象并填充数据
                Employee employee = new Employee();

                // 处理ID列
                if (idCell != null) {
                    if (idCell.getCellType() == CellType.NUMERIC) {
                        employee.setId((int) idCell.getNumericCellValue());
                    } else if (idCell.getCellType() == CellType.STRING) {
                        try {
                            employee.setId(Integer.parseInt(idCell.getStringCellValue()));
                        } catch (NumberFormatException e) {
                            System.err.println("无效的ID格式在行 " + (i + 1) + ": " + idCell.getStringCellValue());
                            continue;
                        }
                    }
                }

                // 处理姓名列
                if (nameCell != null) {
                    if (nameCell.getCellType() == CellType.STRING) {
                        employee.setName(nameCell.getStringCellValue());
                    } else if (nameCell.getCellType() == CellType.NUMERIC) {
                        employee.setName(String.valueOf((int) nameCell.getNumericCellValue()));
                    }
                }

                // 处理性别列
                if (genderCell != null) {
                    if (genderCell.getCellType() == CellType.STRING) {
                        employee.setGender(genderCell.getStringCellValue());
                    } else if (genderCell.getCellType() == CellType.NUMERIC) {
                        employee.setGender(String.valueOf((int) genderCell.getNumericCellValue()));
                    }
                }

                // 处理部门列
                if (departmentCell != null) {
                    if (departmentCell.getCellType() == CellType.STRING) {
                        employee.setDepartment(departmentCell.getStringCellValue());
                    } else if (departmentCell.getCellType() == CellType.NUMERIC) {
                        employee.setDepartment(String.valueOf((int) departmentCell.getNumericCellValue()));
                    }
                }

                // 处理职位列
                if (positionCell != null) {
                    if (positionCell.getCellType() == CellType.STRING) {
                        employee.setPosition(positionCell.getStringCellValue());
                    } else if (positionCell.getCellType() == CellType.NUMERIC) {
                        employee.setPosition(String.valueOf((int) positionCell.getNumericCellValue()));
                    }
                }

                // 处理薪资列
                if (salaryCell != null) {
                    if (salaryCell.getCellType() == CellType.NUMERIC) {
                        employee.setSalary((int) salaryCell.getNumericCellValue());
                    } else if (salaryCell.getCellType() == CellType.STRING) {
                        try {
                            employee.setSalary(Integer.parseInt(salaryCell.getStringCellValue()));
                        } catch (NumberFormatException e) {
                            System.err.println("无效的薪资格式在行 " + (i + 1) + ": " + salaryCell.getStringCellValue());
                        }
                    }
                }

                // 处理奖金列
                if (bonusCell != null) {
                    if (bonusCell.getCellType() == CellType.NUMERIC) {
                        employee.setBonus((int) bonusCell.getNumericCellValue());
                    } else if (bonusCell.getCellType() == CellType.STRING) {
                        try {
                            employee.setBonus(Integer.parseInt(bonusCell.getStringCellValue()));
                        } catch (NumberFormatException e) {
                            System.err.println("无效的奖金格式在行 " + (i + 1) + ": " + bonusCell.getStringCellValue());
                        }
                    }
                }

                // 验证必要字段
                if (employee.getName() == null || employee.getName().isEmpty()) {
                    System.err.println("跳过无效记录，行 " + (i + 1) + "：姓名为空");
                    continue;
                }

                // 将员工信息添加到系统中
                Boolean result = addEmployee(employee);
                if (!result) {
                    // 如果添加失败，可能是ID冲突，尝试更新
                    updateEmployee(employee);
                    System.out.println("更新员工信息: " + employee.getName());
                } else {
                    System.out.println("添加员工信息: " + employee.getName());
                }
            }

            System.out.println("员工信息已成功从文件读取：" + filePath);
        }  catch (IOException e) {
            throw new RuntimeException("读取员工信息失败：" + e.getMessage(), e);
        } catch (Exception e) {
            throw new RuntimeException("解析员工信息时发生错误：" + e.getMessage(), e);
        }
    }
    public void saveInfoToFile(String filePath) throws IOException {
        // 获取所有员工信息
        List<Employee> employees = listAllDeptOrPosOrEmpInfo(Employee.class);

        if (employees.isEmpty()) {
            throw new IOException("没有员工数据可导出！");
        }

        // 确保文件扩展名为.xlsx
        if (!filePath.toLowerCase().endsWith(".xlsx")) {
            filePath += ".xlsx";
        }

        // 创建工作簿
        try (Workbook workbook = new XSSFWorkbook()) {
            // 创建工作表
            Sheet sheet = workbook.createSheet("员工信息");

            // 创建表头
            Row headerRow = sheet.createRow(0);
            String[] headers = {"ID", "姓名", "性别", "部门", "职位", "薪资", "奖金"};

            for (int i = 0; i < headers.length; i++) {
                Cell cell = headerRow.createCell(i);
                cell.setCellValue(headers[i]);
            }

            // 写入员工数据
            for (int i = 0; i < employees.size(); i++) {
                Employee employee = employees.get(i);
                Row row = sheet.createRow(i + 1);

                row.createCell(0).setCellValue(employee.getId());
                row.createCell(1).setCellValue(employee.getName());
                row.createCell(2).setCellValue(employee.getGender());
                row.createCell(3).setCellValue(employee.getDepartment());
                row.createCell(4).setCellValue(employee.getPosition());
                row.createCell(5).setCellValue(employee.getSalary());
                row.createCell(6).setCellValue(employee.getBonus());
            }

            // 检查文件是否已存在
            Path path = Paths.get(filePath);
            if (Files.exists(path)) {
                // 如果文件存在，先删除
                Files.delete(path);
            }

            // 写入文件
            try (FileOutputStream fileOut = new FileOutputStream(filePath)) {
                workbook.write(fileOut);
            }
        }
    }



}
